package ru.ruappmaker.calendar;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.GregorianCalendar;
import java.util.HashMap;
import java.util.List;

import com.flurry.android.FlurryAgent;
import ru.ruappmaker.calendar.R;

import android.app.AlertDialog;
import android.app.Application;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.SharedPreferences.Editor;
import android.content.res.Resources.Theme;
import android.content.res.TypedArray;
import android.graphics.Color;
import android.graphics.Typeface;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import android.support.v7.app.ActionBarActivity;
import android.util.TypedValue;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.LinearLayout;
import android.widget.TextView;
import android.widget.LinearLayout.LayoutParams;
import android.widget.Toast;

public class CalendarActivity extends ActionBarActivity {
	private int monthColor;
		private int holidayColor;
	private int shortdayColor;
	AlertDialog levelDialog;
	private Context context;
	private float textSize = 11;
	protected int _year = 0;
    protected int year() {
        if (_year == 0)
            _year = Calendar.getInstance().get(Calendar.YEAR);
        return _year;
    }
	protected List<Integer>[] holyDays;
	protected List<Integer>[] shortDays;
	protected ArrayList<MonthInfo> monthInfo;

	private final String[] weekdays = new String[] { "Пн", "Вт", "Ср", "Чт",
			"Пт", "Сб", "Вс" };

	private final int[] daysPerMonths = { 31, 28, 31, 30, 31, 30, 31, 31, 30,
			31, 30, 31 };
	private int daysInMonth;

	protected Theme theme = null;
	
	protected class MonthInfo {
		public int calDays, workDays, holiDays;
		String work40, work36, work24;

		public MonthInfo(int cd, int wd, int hd, String w40, String w36,
				String w24) {
			calDays = cd;
			workDays = wd;
			holiDays = hd;
			work40 = w40;
			work36 = w36;
			work24 = w24;
		}
	}

	private class GridCell {
		public String Text;
		public int Color;
		public int BackgroundColor;
		public boolean Bold;

		public GridCell(String text, int color, int backgroundColor,
				Boolean hasBorder, int weight) {
			Text = text;
			Color = color;
			BackgroundColor = backgroundColor;
			Bold = false;
		}
	}
	
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		ApplySavedTheme();
	}
	
	protected void ApplySavedTheme() {
		SharedPreferences settings = getSharedPreferences("RuappMakerCal", 0);
		String savedTheme = settings.getString("colorSchema", "Blue");
		int themeId = GetThemeByName(savedTheme);
		setTheme(themeId);
	}
	
	protected int GetThemeByName(String theme) {
		if (theme.equals("Blue"))
			return R.style.MainThemeBlue;
	else if (theme.equals("Red"))
			return R.style.MainThemeRed;
	else 
			return R.style.MainThemeBlue;
	}
	
	protected LinearLayout createCalendar(LinearLayout calTable, int month,
			int year, boolean singleWeek) {
		
		ArrayList<GridCell> list = new ArrayList<GridCell>();
		Calendar calendar = Calendar.getInstance();
		// The number of days to leave blank at
		// the start of this month.
		int trailingSpaces = 0;
		int daysInPrevMonth = 0;
		int currentMonth = month - 1;
		int timeMonth = calendar.get(Calendar.MONTH);
		int timeYear = calendar.get(Calendar.YEAR);
		int timeDay = calendar.get(Calendar.DAY_OF_MONTH);
		int dayColor;
		int trailingDayColor = getResources().getColor(R.color.trailing_day);
		Calendar monthCal = Calendar.getInstance();
		monthCal.set(year, month - 1, 1);
		int weekOfYear = monthCal.get(Calendar.WEEK_OF_YEAR);

		holidayColor = monthColor = getColorByAttribute(R.attr.themeColor);
		shortdayColor = getColorByAttribute(R.attr.themeLightColor);
		dayColor = getColorByAttribute(R.attr.themeDayColor);
		
		// String currentMonthName = months[currentMonth];
		daysInMonth = daysPerMonths[currentMonth];
		context = getApplicationContext();
		GregorianCalendar cal = new GregorianCalendar(year, currentMonth, 1);

		if (currentMonth == 0)
			daysInPrevMonth = daysPerMonths[11];
		else
			daysInPrevMonth = daysPerMonths[currentMonth - 1];

		// Compute how much to leave before before the first day of the
		// month.
		// getDay() returns 0 for Sunday.
		int currentWeekDay = cal.get(Calendar.DAY_OF_WEEK) - 2;
		if (currentWeekDay < 0)
			currentWeekDay = 6;
		trailingSpaces = currentWeekDay;

		if (cal.isLeapYear(cal.get(Calendar.YEAR)) && month == 1) {
			++daysInMonth;
		}

		// Trailing Month days
		for (int i = 1; i <= trailingSpaces; i++) {
			list.add(new GridCell(String.valueOf(daysInPrevMonth
					- trailingSpaces + i), trailingDayColor, Color.TRANSPARENT, true, 1));
		}

		// Current Month Days
		for (int i = 1; i <= daysInMonth; i++) {
			GridCell cell = new GridCell(String.valueOf(i), dayColor, Color.TRANSPARENT, true, 1);
			if (i == timeDay && timeMonth == currentMonth && timeYear == year) {
				cell.Color = Color.WHITE;
				cell.BackgroundColor = monthColor;
			}
			else if (holyDays[currentMonth] != null
					&& holyDays[currentMonth].contains(i)) {
				cell.Color = holidayColor;
				cell.Bold = true;
			}
			else if (shortDays[currentMonth] != null
					&& shortDays[currentMonth].contains(i)) {
				cell.Color = shortdayColor;
				cell.Bold = true;
			}
			list.add(cell);
		}

		for (int i = 0; i < list.size() % 7; i++) {
			list.add(new GridCell(String.valueOf(i + 1), trailingDayColor, Color.TRANSPARENT, true, 1));
		}

		int rowsCount = list.size() / 7;

		LayoutInflater inflater = (LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE);

		LinearLayout.LayoutParams rowParams = new LinearLayout.LayoutParams(
				LinearLayout.LayoutParams.FILL_PARENT,
				LinearLayout.LayoutParams.WRAP_CONTENT);
		LinearLayout header = new LinearLayout(context);
		header.setOrientation(LinearLayout.HORIZONTAL);
		header.setLayoutParams(rowParams);
		int cellsCount = singleWeek ? 7:8;
		
		for (int i = -1; i < cellsCount; i++) {
			TextView dayCell = new TextView(context);
			dayCell.setBackgroundColor(monthColor);
			dayCell.setTypeface(Typeface.DEFAULT_BOLD);
			dayCell.setTextSize(textSize);
			LinearLayout.LayoutParams cellParams = new LinearLayout.LayoutParams(
					0, LayoutParams.WRAP_CONTENT, 1.0f);
			if (i == -1 || i == 7) {
				cellParams.weight = 1.5f;
			} else {
				dayCell.setText(String.format(weekdays[i]));
				dayCell.setTextColor(Color.WHITE);
			}
			dayCell.setLayoutParams(cellParams);
			dayCell.setGravity(Gravity.CENTER);
			header.addView(dayCell);
		}
		calTable.addView(header);

		for (int row = 0; row < rowsCount; row++) {
			LinearLayout tRow = new LinearLayout(context);

			tRow.setLayoutParams(rowParams);
			tRow.addView(createWeekCell(weekOfYear, true));

			for (int i = 0; i < 7; i++) {
				LinearLayout cellView = (LinearLayout) inflater.inflate(
						R.layout.day_cell, null);
				TextView tView = (TextView) cellView
						.findViewById(R.id.day_text);
				int idx = row * 7 + i;
				GridCell cell = list.get(idx);
				tView.setText(String.format(cell.Text));
				if (cell.Color != trailingDayColor && i > 4 && cell.Color != Color.WHITE) {
					tView.setTextColor(holidayColor);
					tView.setTypeface(null, Typeface.BOLD);
				}
				else  {
					tView.setTextColor(cell.Color);
					if (cell.Bold) tView.setTypeface(null, Typeface.BOLD);
				}
				
				cellView.setLayoutParams(new LinearLayout.LayoutParams(0,
						LayoutParams.WRAP_CONTENT, 1.0f));
				GradientDrawable bg = (GradientDrawable) tView.getBackground();
				bg.setColor(cell.BackgroundColor);
				tRow.addView(cellView);
			}
			if (!singleWeek)
				tRow.addView(createWeekCell(weekOfYear, false));
			calTable.addView(tRow);
			weekOfYear++;
		}
		return calTable;
	}

	private TextView createWeekCell(int week, boolean left) {
		int cellColor = getResources().getColor(R.color.trailing_day);
		TextView tViewWeek = new TextView(context);
		tViewWeek.setLayoutParams(new LinearLayout.LayoutParams(0,
				LayoutParams.FILL_PARENT, 1.5f));
		tViewWeek.setText(String.format("%02d", week));
		tViewWeek.setTextColor(cellColor);
		tViewWeek.setGravity(Gravity.CENTER);
		tViewWeek.setTypeface(Typeface.DEFAULT_BOLD);
		
		tViewWeek.setBackgroundDrawable(getResources().getDrawable(left ? R.drawable.right_border : R.drawable.left_border));
		tViewWeek.setTextSize(textSize);
		return tViewWeek;
	}

	private void FillListFromString(String dates, List<Integer>[] array) {
		String[] RowData = dates.split(";");
		for (int i = 0; i < RowData.length; i++) {
			String[] dateParts = RowData[i].split("\\.");
			int dateDay = Integer.valueOf(dateParts[0]);
			int dateMonth = Integer.valueOf(dateParts[1]) - 1;
			if (array[dateMonth] == null)
				array[dateMonth] = new ArrayList<Integer>();
			array[dateMonth].add(dateDay);
		}
	}

	protected void FillDataArrays() {
		monthInfo = new ArrayList<MonthInfo>();
		holyDays = (List<Integer>[]) new ArrayList[12];
		shortDays = (List<Integer>[]) new ArrayList[12];
        int year = year();
		InputStream dataFile = getResources().openRawResource(
				year == 2013 ? R.raw.cal2013 : (year == 2014 ? R.raw.cal2014 : R.raw.cal2015));
		BufferedReader dataReader = new BufferedReader(new InputStreamReader(
				dataFile));

		try {
			String line;
			if ((line = dataReader.readLine()) != null)
				FillListFromString(line, holyDays);
			if ((line = dataReader.readLine()) != null)
				FillListFromString(line, shortDays);
			for (int i = 0; i < 12; i++) {
				line = dataReader.readLine();
				String[] info = line.split(";");
				monthInfo.add(new MonthInfo(Integer.valueOf(info[0]), Integer
						.valueOf(info[1]), Integer.valueOf(info[2]), 
						roundDouble(Double.valueOf(info[3])), 
						roundDouble(Double.valueOf(info[4])), 
						roundDouble(Double.valueOf(info[5])))); 
			}
		} catch (IOException ex) {
			// handle exception
		} finally {
			try {
				dataFile.close();
			} catch (IOException e) {
				// handle exception
			}
		}
	}
	
	@Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.main, menu);
        return true;
    }
	
	private String roundDouble(double d) {
		return (long) d == d ? "" + (long) d : "" + d; 
	}
	
	protected void LeaveResponse() {
		Intent i = new Intent(Intent.ACTION_SEND);
		i.setType("message/rfc822");
		i.putExtra(Intent.EXTRA_EMAIL  , new String[]{"ruappmaker@gmail.com"});
		i.putExtra(Intent.EXTRA_SUBJECT, "Производственный календарь");
		i.putExtra(Intent.EXTRA_TEXT   , "");
		try {
		    startActivity(Intent.createChooser(i, "Send mail..."));
		} catch (android.content.ActivityNotFoundException ex) {
		    Toast.makeText(this.context, "There are no email clients installed.", Toast.LENGTH_SHORT).show();
		}
		
	}
	
	private boolean changeYear(int newyear) {
		if (year() != newyear) {
			_year = newyear;
			FlurryAgent.logEvent("Year changed in " + getSubClassObject().getClass().getName());
			InitViewPager();
		}
		return (true);
	}
	
	@Override
	public boolean onOptionsItemSelected(MenuItem item) {
		switch (item.getItemId()) {
		case R.id.year2013:
			return (changeYear(2013));
		case R.id.year2014:
			return (changeYear(2014));
		case R.id.year2015:
			return (changeYear(2015));
		case R.id.about:
			FlurryAgent.logEvent("User is about to leave response");
			LeaveResponse();
			return true;
		case R.id.theme:
			
			final CharSequence[] items = {" Синяя "," Красная "};
			AlertDialog.Builder builder = new AlertDialog.Builder(this);
            builder.setTitle("Выберите тему");
            builder.setSingleChoiceItems(items, -1, new DialogInterface.OnClickListener() {
            public void onClick(DialogInterface dialog, int item) {
            	SharedPreferences settings = getSharedPreferences("RuappMakerCal", 0);
        		Editor ed = settings.edit();
                switch(item)
                {
                    case 0:
                            ed.putString("colorSchema", "Blue");
                            ed.commit();
                            RestartThis();
                            break;
                    case 1:
                    	ed.putString("colorSchema", "Red");
                        ed.commit();
                    	RestartThis();
                        break;
                    
                }
                levelDialog.dismiss();    
                }
            });
            levelDialog = builder.create();
            levelDialog.show();
		}
		return (super.onOptionsItemSelected(item));
	}
	
	protected void InitViewPager() { return ; }
	
	@Override
	protected void onStart()
	{
		super.onStart();
		theme = getTheme();
		FlurryAgent.onStartSession(getSubClassObject(), "Y3STGWMB73XJXFWSNW8P");
		FlurryAgent.logEvent("Started activity: " + getSubClassObject().getClass().getName());
	}
	 
	@Override
	protected void onStop()
	{
		super.onStop();		
		FlurryAgent.onEndSession(getSubClassObject());
	}
	
	protected Context getSubClassObject() {
		return this instanceof MainActivity? (MainActivity)this : (MonthView) this;
	}
	
	protected int getColorByAttribute(int attr){
		if (theme == null) theme = getTheme();
		   TypedValue typedvalueattr = new TypedValue();
		   theme.resolveAttribute(attr, typedvalueattr, true);
		   return getResources().getColor(typedvalueattr.resourceId);
		
	}
	
	protected void RestartThis() {
		return;
	}
	
}
